package middleware

import (
	"fmt"
	"github.com/gin-gonic/gin"
	retalog "github.com/lestrrat-go/file-rotatelogs"
	"github.com/rifflock/lfshook"
	"github.com/sirupsen/logrus"
	"math"
	"os"
	"time"
)

func Logger() gin.HandlerFunc  {
	filePath := "log/log"
	//linkName := "latest_log.log"
	src, err :=  os.OpenFile(filePath,os.O_RDWR|os.O_CREATE, 0755)
	if err != nil {
		fmt.Println("err", err)
	}
	logger := logrus.New()
	logger.Out = src
	logger.SetLevel(logrus.DebugLevel)

	logWriter, _ := retalog.New(
		filePath+"%Y%m%d.log",
		retalog.WithMaxAge(7*24*time.Hour),
		retalog.WithRotationTime(24*time.Hour),
		// 建立软连接
		//retalog.WithLinkName(linkName),
		)
	writeMap := lfshook.WriterMap{
		logrus.InfoLevel: logWriter,
		logrus.FatalLevel: logWriter,
		logrus.DebugLevel: logWriter,
		logrus.WarnLevel: logWriter,
		logrus.ErrorLevel: logWriter,
		logrus.PanicLevel: logWriter,
	}
	Hook :=  lfshook.NewHook(writeMap,&logrus.TextFormatter{
		TimestampFormat: "2006-01-02 15:04:05",
	})
	logger.AddHook(Hook)
	return func(c *gin.Context) {
		startTime := time.Now()
		// 执行下一个中间件 必须调用c.Next()
		c.Next()
		stopTime := time.Since(startTime)
		// 开销时间
		spendTime := fmt.Sprintf("%d ms", int(math.Ceil(float64(stopTime.Nanoseconds()) / 1000000.0)))
		hostName,err := os.Hostname()
		if err != nil {
			hostName = "unknown"
		}
		// 状态码
		statusCode := c.Writer.Status()
		// IP
		clientIp := c.ClientIP()
		// 客户端信息
		userAgent := c.Request.UserAgent()
		// 文件大小
		dataSize := c.Writer.Size()
		if dataSize < 0 {
			dataSize = 0
		}
		// 请求方法
		method := c.Request.Method
		// 请求路径
		path := c.Request.RequestURI

		entry := logger.WithFields(logrus.Fields{
			"HostName":hostName,
			"Status":statusCode,
			"SpendTime":spendTime,
			"IP":clientIp,
			"Path":path,
			"DataSize":dataSize,
			"Method":method,
			"Agent":userAgent,
		})
		if len(c.Errors) > 0 {
			entry.Error(c.Errors.ByType(gin.ErrorTypePrivate).String())
		}

		if statusCode >= 500 {
			entry.Error()
		} else if statusCode >= 400 {
			entry.Warn()
		} else {
			entry.Info()
		}

	}
}
